#include "stdafx.h"
#include "net/HTTPStream.hpp"

NET_NAMESPACE_BEGIN

//
// CHTTPStreamBuf
//
CHTTPStreamBuf::CHTTPStreamBuf(CHTTPSession& session, openmode mode)
	: HTTPBasicStreamBuf(CHTTPBufferAllocator::BUFFER_SIZE, mode),
	m_session(session),
	m_mode(mode)
{
}

CHTTPStreamBuf::~CHTTPStreamBuf()
{
}

void CHTTPStreamBuf::close()
{
	if (m_mode & std::ios::out)
	{
		sync();
		m_session.socket().shutdownSend();
	}
}

int CHTTPStreamBuf::readFromDevice(char* buffer, std::streamsize length)
{
	return m_session.read(buffer, length);
}

int CHTTPStreamBuf::writeToDevice(const char* buffer, std::streamsize length)
{
	return m_session.write(buffer, length);
}


//
// CHTTPIOS
//
CHTTPIOS::CHTTPIOS(CHTTPSession& session, CHTTPStreamBuf::openmode mode) : m_buf(session, mode)
{
	
}

CHTTPIOS::~CHTTPIOS()
{
	try
	{
		m_buf.close();
	}
	catch (...)
	{
	}
}

CHTTPStreamBuf* CHTTPIOS::rdbuf()
{
	return &m_buf;
}


//
// CHTTPInputStream
//
CMemoryPool CHTTPInputStream::m_pool(sizeof(CHTTPInputStream));

CHTTPInputStream::CHTTPInputStream(CHTTPSession& session)
	: CHTTPIOS(session, std::ios::in),
	std::istream(&m_buf)
{
}

CHTTPInputStream::~CHTTPInputStream()
{
}

void* CHTTPInputStream::operator new(std::size_t size)
{
	return m_pool.get();
}

void CHTTPInputStream::operator delete(void* ptr)
{
	try
	{
		m_pool.release(ptr);
	}
	catch (...)
	{
		jh_unexpected();
	}
}


//
// CHTTPOutputStream
//
CMemoryPool CHTTPOutputStream::m_pool(sizeof(CHTTPOutputStream));

CHTTPOutputStream::CHTTPOutputStream(CHTTPSession& session)
	: CHTTPIOS(session, std::ios::out),
	std::ostream(&m_buf)
{
}

CHTTPOutputStream::~CHTTPOutputStream()
{
}

void* CHTTPOutputStream::operator new(std::size_t size)
{
	return m_pool.get();
}

void CHTTPOutputStream::operator delete(void* ptr)
{
	try
	{
		m_pool.release(ptr);
	}
	catch (...)
	{
		jh_unexpected();
	}
}

NET_NAMESPACE_END
